// PanelSort.cpp

#include "StdAfx.h"

#include "Panel.h"

#include "Common/MS/PropVariant.h"
#include "Common/7Zip/PropID.h"
#include "Common/Defs.h"



//#include "Common/MyFixes.h"

static CString GetExtension(const CString &name)
{
	int dotPos = name.ReverseFind(L'.');
	if (dotPos < 0)
	{
		return CString();
	}
	return name.Mid(dotPos);
}

int CALLBACK CompareItems2(LPARAM lParam1, LPARAM lParam2, LPARAM lpData)
{
	if (lpData == NULL)
	{
		return 0;
	}
	CPanel* panel = (CPanel*)lpData;

	switch(panel->_sortID)
	{
		case kpidName:
		{
			const CString name1 = panel->m_directory.GetItemName((int)lParam1);
			const CString name2 = panel->m_directory.GetItemName((int)lParam2);
			int res = name1.CompareNoCase(name2);
			return res;
		}
		case kpidNoProperty:
		{
			return simpleCompare(lParam1, lParam2);
		}
		case kpidExtension:
		{
			const CString ext1 = GetExtension(panel->m_directory.GetItemName((int)lParam1));
			const CString ext2 = GetExtension(panel->m_directory.GetItemName((int)lParam2));
			return ext1.CompareNoCase(ext2);
		}
	}
	PROPID propID = panel->_sortID;

	CComPropVariant prop1, prop2;
	// Name must be first property
	panel->m_directory.GetIFolder()->GetProperty((UINT32)lParam1, propID, &prop1);
	panel->m_directory.GetIFolder()->GetProperty((UINT32)lParam2, propID, &prop2);
	if (prop1.vt != prop2.vt)
	{
		return simpleCompare(prop1.vt, prop2.vt);
	}
	if (prop1.vt == VT_BSTR)
	{
		return _wcsicmp(prop1.bstrVal, prop2.bstrVal);
	}
	return prop1.Compare(prop2);
}

int CALLBACK CompareItems(LPARAM lParam1, LPARAM lParam2, LPARAM lpData)
{
	if (lpData == NULL)
	{
		return 0;
	}
	if (lParam1 == FileManager::FileSystem::kParentIndex)
	{
		return -1;
	}
	if (lParam2 == FileManager::FileSystem::kParentIndex)
	{
		return 1;
	}

	CPanel* panel = (CPanel*)lpData;

	bool isDir1 = panel->m_directory.IsItemFolder((int)lParam1);
	bool isDir2 = panel->m_directory.IsItemFolder((int)lParam2);

	if (isDir1 && !isDir2)
	{
		return -1;
	}
	if (isDir2 && !isDir1)
	{
		return 1;
	}

	int result = CompareItems2(lParam1, lParam2, lpData);
	return panel->_ascending ? result : (-result);
}


void CPanel::SortItemsWithPropID(PROPID propID)
{
	if (propID == _sortID)
	{
		_ascending = !_ascending;
	}
	else
	{
		_sortID = propID;
		_ascending = true;
		switch (propID)
		{
			case kpidSize:
			case kpidPackSize:
			case kpidCTime:
			case kpidATime:
			case kpidMTime:
				_ascending = false;
				break;
		}
	}
	_listView.SortItems(CompareItems, (LPARAM)this);
	_listView.EnsureVisible(_listView.GetNextItem(-1, LVNI_FOCUSED), false);
}


void CPanel::OnColumnClick(LPNMLISTVIEW info)
{

	SortItemsWithPropID(m_directory.GetVisibleProperties()[info->iSubItem].ID);
}
